package org.qloudgen.borg.pages.panel;

import java.util.ArrayList;

import org.apache.commons.lang.StringUtils;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.apache.wicket.ajax.AjaxRequestTarget;
import org.apache.wicket.ajax.form.AjaxFormComponentUpdatingBehavior;
import org.apache.wicket.ajax.markup.html.AjaxLink;
import org.apache.wicket.ajax.markup.html.form.AjaxButton;
import org.apache.wicket.extensions.ajax.markup.html.modal.ModalWindow;
import org.apache.wicket.markup.html.WebMarkupContainer;
import org.apache.wicket.markup.html.form.ChoiceRenderer;
import org.apache.wicket.markup.html.form.DropDownChoice;
import org.apache.wicket.markup.html.form.Form;
import org.apache.wicket.markup.html.form.RequiredTextField;
import org.apache.wicket.markup.html.form.TextField;
import org.apache.wicket.markup.html.panel.Panel;
import org.apache.wicket.model.CompoundPropertyModel;
import org.qloudgen.borg.CommonValues;
import org.qloudgen.borg.beans.FuncBean;
import org.qloudgen.borg.beans.ParamBean;
import org.qloudgen.borg.utils.Validation;

@SuppressWarnings({ "rawtypes", "unchecked" })
public class AddFuncParameterPanel extends Panel {

	static Log log = LogFactory.getLog(AddFuncParameterPanel.class);
	private static final long serialVersionUID = 1L;
	
	public AddFuncParameterPanel(String id, final FuncBean func , final ModalWindow window) {
		
		super(id);

		final WebMarkupContainer selectBorder = new WebMarkupContainer("selectBorder");
		selectBorder.setOutputMarkupId(true);
		
		final WebMarkupContainer inputBorder = new WebMarkupContainer("inputBorder");
		inputBorder.setOutputMarkupId(true);
		
		final WebMarkupContainer selectInfo = new WebMarkupContainer("selectInfo");
		selectInfo.setOutputMarkupId(true);
		selectInfo.setVisible(false);
		selectBorder.add(selectInfo);
		
		final WebMarkupContainer inputInfo = new WebMarkupContainer("inputInfo");
		inputInfo.setOutputMarkupId(true);
		inputInfo.setVisible(true);
		inputBorder.add(inputInfo);
		
		final Form<?> form = new Form("form",new CompoundPropertyModel<ParamBean>(new ParamBean().setParamType(2))) {
			
			private static final long serialVersionUID = 1L;

			protected void onSubmit() {
				ParamBean param = (ParamBean)getDefaultModelObject();
				ParamBean newParam = param.clone();
						
				if (checkParam(func,newParam) && packageParam(newParam)) {
					func.getParams().add(newParam);
				}
			}
			
		};
		this.add(form);
		
		form.add(new RequiredTextField<String>("paramCode"));
		form.add(new RequiredTextField<String>("paramName"));
		form.add(new TextField<String>("paramDesc"));
		form.add(selectBorder);
		form.add(inputBorder);
		
		// select components
		selectInfo.add(new TextField<String>("values").setOutputMarkupId(true));
		selectInfo.add(new TextField<String>("names").setOutputMarkupId(true));
		
		// input components
		inputInfo.add(new TextField<String>("lengthCheck").setOutputMarkupId(true));
		inputInfo.add(new DropDownChoice<String>("dateCheck", CommonValues.dateFormats).setOutputMarkupId(true));
		inputInfo.add(new DropDownChoice<String>("digitCheck", new ArrayList(CommonValues.booleanNames.keySet()),
				new ChoiceRenderer<Object>(){
					private static final long serialVersionUID = 1L;
					public Object getDisplayValue(Object object) {
						return CommonValues.booleanNames.get(object);
					}
				}
		).setOutputMarkupId(true));
//		inputInfo.add(new TextField<String>("rangeCheck").setOutputMarkupId(true));
		
		// param type
		DropDownChoice<String> paramType = new DropDownChoice<String>("paramType", new ArrayList(CommonValues.paramTypes.keySet()),
				new ChoiceRenderer<Object>(){
					private static final long serialVersionUID = 1L;
					public Object getDisplayValue(Object object) {
						return CommonValues.paramTypes.get(object);
					}
				}
		);
		form.add(paramType);
		
		AjaxFormComponentUpdatingBehavior behavior = new AjaxFormComponentUpdatingBehavior("onChange"){

			private static final long serialVersionUID = 1L;
			protected void onUpdate(AjaxRequestTarget target) {
				
				int value = ((Integer)getFormComponent().getDefaultModelObject()).intValue() ;
				
				switch (value){
					case 1 : { selectInfo.setVisible(true);inputInfo.setVisible(false);break; }
					case 2 : { inputInfo.setVisible(true);selectInfo.setVisible(false);break; }
				}
				
				target.add(selectBorder);
				target.add(inputBorder);
				
			}
		};
		paramType.add(behavior);
				
		// button submit 
		form.add(new AjaxButton("confirm"){

			private static final long serialVersionUID = 1L;
			protected void onAfterSubmit(AjaxRequestTarget target, Form<?> form) {
				if (window != null)	window.close(target);
			}
		});
		
		// button cancel
		form.add(new AjaxLink<Void>("cancel"){
			
			private static final long serialVersionUID = 1L;
			public void onClick(AjaxRequestTarget target) {
				if (window != null)	window.close(target);
			}});

	}

	protected boolean packageParam(ParamBean param) {
		
		if (param.getParamType() == 0) return false;
		
		switch (param.getParamType()){
			case 1 : {
				if (StringUtils.isBlank(param.getValues()) || StringUtils.isBlank(param.getNames())) return false;
				
				String[] valueArray = param.getValues().split(",");
				String[] nameArray = param.getNames().split(",");
				
				if (valueArray.length != nameArray.length) return false;
				
				for (int i = 0; i < valueArray.length; i++){
					if (StringUtils.isBlank(valueArray[i]) || StringUtils.isBlank(nameArray[i])) return false;
				}
				
				param.setParamInfo(param.getValues() + ";" + param.getNames());
				break;
			}
			case 2 : {
				
				StringBuffer sb = new StringBuffer();
			
				if (Validation.check1(param.getLengthCheck(),",",true)) sb.append(";1#"+param.getLengthCheck());

				if (StringUtils.isNotBlank(param.getDateCheck())) sb.append(";2#"+param.getDateCheck());

				if (StringUtils.isNotBlank(param.getDigitCheck()) && param.getDigitCheck().equalsIgnoreCase("true")) 
						sb.append(";3#"+param.getDigitCheck());

				if (Validation.check1(param.getRangeCheck(),",",true) )	sb.append(";4#"+param.getRangeCheck());

				if (StringUtils.isNotBlank(sb.toString())) param.setParamInfo(sb.toString().substring(1));

				break;
			}
		}

		return true;
	}

	protected boolean checkParam(FuncBean func,ParamBean param) {
		
		for (ParamBean bean : func.getParams()) {
			if (bean.getParamName().equalsIgnoreCase(param.getParamName()) 
					|| bean.getParamCode().equalsIgnoreCase(param.getParamCode()))
				return false;
		}
		
		return true;
	}
}
